﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.Practices.Unity;
using Wyn.PMS.Common.NightAudit;
using Wyn.PMS.Common.Utils;
using Wyn.PMS.Entity.Entities;
using Wyn.PMS.Entity.IDataAccess;

namespace Wyn.PMS.Test.Cache
{
    public class FixHotelRemain
    {
        private static IUnityContainer container = UnityContainerService.GetContainer();

        internal static void RefreshHotelRemain(string hotelId, DateTime bizDay, IList<Entity.Entities.Account> notRollAccounts, System.Transactions.TransactionOptions transactionOptions)
        {
            INaHotelRemainRepository hotelRemainRepository=container.Resolve<INaHotelRemainRepository>();

            var yesterdayRemain = hotelRemainRepository.Find(hotelId, hotelId, bizDay.AddDays(-1));

            NaHotelRemain hotelRemain = new NaHotelRemain
                                            {
                                                HotelID = hotelId,
                                                BizDay = bizDay,
                                                BizDayStart = bizDay.Date,
                                                BizDayEnd = DateTime.Now
                                            };

            hotelRemain.BeginRemain = yesterdayRemain != null
                                          ? yesterdayRemain.BeginRemain + yesterdayRemain.Occur - yesterdayRemain.Receive + Math.Abs(yesterdayRemain.Rebate)
                                          : 0;

            hotelRemain.Occur= notRollAccounts.Where(a => a.LedgerType == AccountType.D).Sum(a => a.Balance);

            hotelRemain.Receive =notRollAccounts.Where(a => a.LedgerType == AccountType.C && a.Balance > 0).Sum(a => a.Balance);

            hotelRemain.Rebate =notRollAccounts.Where(a => a.LedgerType == AccountType.C && a.Balance < 0).Sum(a => a.Balance);

            hotelRemain.Remain=hotelRemain.Receive + hotelRemain.Rebate - hotelRemain.Occur;

            hotelRemain.AllRoomPrice = SumRoomTypePrice(hotelId,bizDay);//5180483的房间总价值  

            var oldRemain= hotelRemainRepository.Find(hotelId, hotelId, bizDay);

            if (oldRemain != null)
            {
                oldRemain.BeginRemain = hotelRemain.BeginRemain;
                oldRemain.Occur = hotelRemain.Occur;
                oldRemain.Receive = hotelRemain.Receive;
                oldRemain.Rebate = hotelRemain.Rebate;
                hotelRemainRepository.Update(oldRemain);
            }else
            {
                hotelRemainRepository.Insert(hotelRemain);
            }

        }

        private static decimal SumRoomTypePrice(string hotelId, DateTime bizDay)
        {
            INaOperationStatusRepository statusRepository = container.Resolve<INaOperationStatusRepository>();

            DateTime yesterDay = bizDay.AddDays(-1);

            PriceCache pc = PriceCache.GetInstance();

            IList<NaOperationStatus> yesterDayStates = statusRepository.BatchFind(hotelId, s => s.HotelID == hotelId && bizDay == yesterDay);

            decimal allPrice = 0;

            if (yesterDayStates != null && yesterDayStates.Count > 0)
            {
                foreach (var state in yesterDayStates)
                {
                    var rooms = state.Count - state.OOOCount;

                    decimal price = pc.GetRoomPrice(hotelId, state.RoomTypeID, bizDay);

                    allPrice += rooms * price;
                }
            }
            else
            {
                IRoomTypeRepository rtr = container.Resolve<IRoomTypeRepository>();

                var roomtypes = rtr.BatchFind(hotelId, r => r.HotelID == hotelId && r.IsValid == true);

                foreach (var roomType in roomtypes)
                {
                    var rooms = roomType.TotalRooms;

                    decimal price = pc.GetRoomPrice(hotelId, roomType.RoomTypeID, bizDay);

                    allPrice += rooms * price;
                }
            }

            return allPrice;
        }
    }
}
